<?php
/**
 * <pre>
 * <b>RUBIK IT Solution & Development ltd.</b>
 *
 * PROJECT      : rubik-base
 * COPYRIGHT    : 2008
 * ------------------------------------------------------
 *
 * [GENERAL INFO OF THIS FILE]
 *
 * </pre>
 *
 * @version 		1.0
 * @author			hoadn <hoadn@rubik.com.vn>
 * @access			public
 * @package			[misc]
 *
 * Created on	: May 15, 2008
 */

class RStringHelper {

	/**
	 * Remove the tail of the input string
	 * Ex: removeTail("0123456789", 3) => "0123456"
	 *
	 * @param string $str string need to remove
	 * @param int $len number of character need to be remove
	 * @return string
	 */
	static function removeTail($str, $len) {
		return substr ( $str, 0, strlen ( $str ) - $len );
	}

	/**
	 * Cut first n characters (end with a meaning word)
	 * Ex: cutFirstNChars("Rubik Base Framework is building.", 7) ==> "Rubik Base ...."
	 *
	 * @param string $str the string will be cut
	 * @param int $numberOfChars number of char that we want to cut
	 * @param string $moreString the string will be add to the tail if cut string. By default it is " ...."
	 * @param boolean $stripTag should strip tag first?
	 * @return string
	 */
	static function cutFirstNChars($str, $numberOfChars, $moreString = " ....", $stripTag = true) {
		if ($stripTag) {
			$str = strip_tags($str);
		}
		$newText = wordwrap ( $str, $numberOfChars, "__RUBIK__BREAKER_LINE__" );
		$newText = substr ( $newText, 0, strpos ( $newText, "__RUBIK__BREAKER_LINE__" ) );
		$newText .= $moreString;
		return $newText;
	}

	/**
	 * Cut first n characters (end with a meaning word)
	 * Ex: cutFirstNChars("Rubik Base Framework is building.", 2) ==> "Rubik Base ...."
	 *
	 * @param string $strCut the string will be cut
	 * @param int $numWordcut number of words that we want to cut
	 * @param string $moreString the string will be add to the tail if cut string. By default it is " ...."
	 * @param string $stripTag should strip tag first?
	 * @return string
	 */
	static function cutFirstNWords($strCut, $numWordcut, $moreString = " ....", $stripTag = true) {
		if ($stripTag) {
			$str = strip_tags($str);
		}
		$strResult = "";
		$arrCut = explode ( " ", $strCut );
		if (count ( $arrCut ) <= $numWordcut) {
			return $strCut;
		}

		for($i = 0; $i < $numWordcut; $i ++) {
			$strResult .= $arrCut [$i];
			$strResult .= " ";
		}
		$moreString = str_word_count ( $strCut, 0 ) > $numWordcut ? $moreString : '';
		$strResult .= $moreString;
		return $strResult;
	}

	/**
	 * The last index of function
	 *
	 * @param string $haystack
	 * @param string $needle
	 * @param int $offset
	 * @return string
	 */
	static function lastIndexOf($haystack, $needle, $offset = 0) {
		$size = strlen ( $haystack );
		$pos = strpos ( strrev ( $haystack ), $needle, $offset );

		if ($pos === false)
		return false;

		return $size - $pos;
	}

	/**
	 * Check the input object is a empty STRING or not.
	 *
	 * @param mixed $str
	 * @return boolean
	 */
	static function isEmpty($str) {
		return strval ( $str ) === '';
	}

	static function getStringByChar($text, $start = 0, $limit = 12, $showMore = true) {
		//		if($text[$limit] != " ")
		//			echo $limit.' '.$text[$limit].'<br>';
		//		while($text[$limit] != " "){
		//			$limit++;
		//		}
		if ($limit < strlen ( $text )) {
			while ( ($text {$limit} != " ") && ($limit > 0) ) {
				$limit --;
			}
		}
		if (function_exists ( "mb_substr" )) {
			$more = (mb_strlen ( $text ) > $limit) ? TRUE : FALSE;
			$text = mb_substr ( $text, 0, $limit, "UTF-8" );
			$moreStr = " ";
			if ($showMore && $more)
			$moreStr = " … ";
				
			return $text . $moreStr;
		} elseif (function_exists ( "iconv_substr" )) {
			$more = (iconv_strlen ( $text ) > $limit) ? TRUE : FALSE;
			$text = iconv_substr ( $text, 0, $limit, "UTF-8" );
			$moreStr = " ";
			if ($showMore && $more)
			$moreStr = " … ";
				
			return $text . $moreStr;
		} else {
			preg_match_all ( "/[\x01-\x7f]|[\xc2-\xdf][\x80-\xbf]|\xe0[\xa0-\xbf][\x80-\xbf]|[\xe1-\xef][\x80-\xbf][\x80-\xbf]|\xf0[\x90-\xbf][\x80-\xbf][\x80-\xbf]|[\xf1-\xf7][\x80-\xbf][\x80-\xbf][\x80-\xbf]/", $text, $ar );
			if (func_num_args () >= 3) {
				if (count ( $ar [0] ) > $limit) {
					$more = TRUE;
					$text = join ( "", array_slice ( $ar [0], 0, $limit ) ) . "…";
				}
				$more = TRUE;
				$text = join ( "", array_slice ( $ar [0], 0, $limit ) );
			} else {
				$more = FALSE;
				$text = join ( "", array_slice ( $ar [0], 0 ) );
			}
			$moreStr = " ";
			if ($showMore && $more)
			$moreStr = " … ";
				
			return $text . $moreStr;
		}
	}

	/**
	 * Generate the code for input string
	 * Ex: input:  "Dang NHON & hoa"
	 * --> output: "dang_nhon_&_hoa"
	 *
	 * @param string $string
	 * @return string
	 */
	static function generateCode($text, $lowercase = true) {
		// Vietnamese processing
		$chars = array ("a", "A", "e", "E", "o", "O", "u", "U", "i", "I", "d", "D", "y", "Y" );
		$uni [0] = array ("á", "à", "ạ", "ả", "ã", "â", "ấ", "ầ", "ậ", "ẩ", "ẫ", "ă", "ắ", "ằ", "ặ", "ẳ", "�  �" );
		$uni [1] = array ("Á", "À", "Ạ", "Ả", "Ã", "Â", "Ấ", "Ầ", "Ậ", "Ẩ", "Ẫ", "Ă", "Ắ", "Ằ", "Ặ", "Ẳ", "�  �" );
		$uni [2] = array ("é", "è", "ẹ", "ẻ", "ẽ", "ê", "ế", "ề", "ệ", "ể", "ễ" );
		$uni [3] = array ("É", "È", "Ẹ", "Ẻ", "Ẽ", "Ê", "Ế", "Ề", "Ệ", "Ể", "Ễ" );
		$uni [4] = array ("ó", "ò", "ọ", "ỏ", "õ", "ô", "ố", "ồ", "ộ", "ổ", "ỗ", "ơ", "ớ", "ờ", "ợ", "ở", "�  �" );
		$uni [5] = array ("Ó", "Ò", "Ọ", "Ỏ", "Õ", "Ô", "Ố", "Ồ", "Ộ", "Ổ", "Ỗ", "Ơ", "Ớ", "Ờ", "Ợ", "Ở", "�  �" );
		$uni [6] = array ("ú", "ù", "ụ", "ủ", "ũ", "ư", "ứ", "ừ", "ự", "ử", "ữ" );
		$uni [7] = array ("Ú", "Ù", "Ụ", "Ủ", "Ũ", "Ư", "Ứ", "Ừ", "Ự", "Ử", "Ữ" );
		$uni [8] = array ("í", "ì", "ị", "ỉ", "ĩ" );
		$uni [9] = array ("Í", "Ì", "Ị", "Ỉ", "Ĩ" );
		$uni [10] = array ("đ" );
		$uni [11] = array ("Đ" );
		$uni [12] = array ("ý", "ỳ", "ỵ", "ỷ", "ỹ" );
		$uni [13] = array ("Ý", "Ỳ", "Ỵ", "Ỷ", "Ỹ" );
		for($i = 0; $i <= 13; $i ++) {
			$text = str_replace ( $uni [$i], $chars [$i], $text );
		}
		if ($lowercase) {
			$text = strtolower($text);
		}

		$text = self::cleanForSeoURL($text);
		return $text;
	}

	/**
	 * Generate a random text with specific len
	 *
	 * @param int $len
	 * @return string the generated text
	 */
	static function generateRandom($len) {
		$possible = "ABCDEFGHIJ3456KLMNOPQRST012679@#$%^abcdefghij34*()!56klmnopqrst0126789";
		while ( strlen ( $str ) < $len ) {
			$char = substr ( $possible, (rand () % (strlen ( $possible ))), 1 );
			$str .= $char;
		}
		return $str;
	}

	/**
	 * Escapes a string so it can be safely echo'ed out as Javascript
	 *
	 * @param  string $str String to escape
	 * @return string      JS Safe string
	 */
	static function escapeString($str) {
		$str = str_replace ( array ('\\', "'" ), array ("\\\\", "\\'" ), $str );
		$str = preg_replace ( '#([\x00-\x1F])#e', '"\x" . sprintf("%02x", ord("\1"))', $str );

		return $str;
	}

	/**
	 * Insert into current string at the last position that macth with the input search criteria
	 * Ex: input
	 *
	 * @param string $string the text to be searched and insert into
	 * @param string $searchStr the search string
	 * @param string $insertStr the insert string
	 */
	static function insertLastMatch($string, $searchStr, $insertStr) {
		$lastPost = RStringHelper::lastIndexOf ( $string, $searchStr );
		if ($lastPost === false) {
			return $lastPost;
		}

		if (empty ( $insertStr )) {
			return $string;
		}

		$result = substr ( $string, 0, $lastPost );
		$result .= $insertStr;
		$result .= substr ( $string, $lastPost );
		return $result;
	}

	/**
	 * Parse String for validator XHTML
	 *
	 * @param string $string
	 * @return $string
	 */
	static function parseXHTML($string) {
		$string = htmlspecialchars($string);
		return $string;
	}

	/**
	 * convert time
	 *
	 * @param str $dateformat
	 * @param str $dateinput
	 * @return date
	 */
	static function convertDateView($dateformat, $dateinput) {
		$timeStamp = strtotime($dateinput);
		return date($dateformat, $timeStamp);
	}

	/**
	 * Check if string is end with the needle
	 *
	 * @param string $string
	 * @param string $needle
	 * @return boolean
	 */
	static function endWith($string, $needle) {
		return strpos($string, $needle) + strlen($needle) == strlen($string);
	}

	/*
	 * Use regular expression to clean url
	 */
	static function cleanForSeoURL($str) {
		$str = strtolower(trim($str));
		$str = preg_replace('/[^a-z0-9-]/', '-', $str);
		$str = preg_replace('/-+/', "-", $str);
		return $str;
	}

	/**
	 * Convert the input html text into the text that we can put it in the attribute value of a tag safely.
	 * Ex: input: <div class="test">The only content we want to get with "quote" inside.</div>
	 * 	output: The only content we want to get with &qoute;quote&qoute; inside.
	 *
	 * @param $text
	 * @return string
	 */
	static function convertToHtmlAttributeValue($text) {
		$text = strip_tags($text);
		$text = htmlspecialchars($text, ENT_QUOTES);
		return $text;
	}

	/**
	 * Remove the slash when php enable mode: magic_quotes_gpc .
	 * Using this static function before set data into view.
	 *
	 * The idea of this: When a form submit then bind value into a DBO (magic_quotes_gpc = on)
	 * if you want to fill data back from current DBO into form --> you must use this static function
	 * for smart strip the slash.
	 *
	 * Why smart?
	 * 	This static function just strip the slash if (magic_quotes_gpc == on)
	 *
	 * @param object or value
	 * @return stripted
	 */
	static function smartStripSlash($objectOrValue) {
		if (! get_magic_quotes_gpc ()) {
			return $objectOrValue;
		}
		if (is_string($objectOrValue)) {
			$objectOrValue = stripcslashes ( $objectOrValue );
		}
		else if (is_object($objectOrValue)) {
			$vars = get_object_vars ( $objectOrValue );
			foreach ( $vars as $k => $v ) {
				$objectOrValue->$k = stripslashes($v);
			}
		}

		return $objectOrValue;
	}
}
?>